#include <stdio.h>
#include<stdlib.h>
#include<conio.h>
#include<windows.h>

#define High 15 //游戏画面尺寸
#define Width 35


//函数外全局变量定义
int food_x,food_y;              //记录食物的位置
int canvas[High][Width]={0};    //二维数组存储游戏画面
//0为空格，-1为边框#，1为蛇头@，>1为蛇身*,-2为食物
int moveDirection;              //小蛇移动方向，1、2、3、4分别表示上下左右


int gotoxy(int x,int y)         //光标移动到（x，y）位置
{
    HANDLE handle=GetStdHandle(STD_OUTPUT_HANDLE);
    COORD pos;
    pos.X=x;
    pos.Y=y;
    SetConsoleCursorPosition(handle,pos);
}

int HideCursor()
{
    CONSOLE_CURSOR_INFO cursor_info = {1,0};
    SetConsoleCursorInfo(GetStdHandle(STD_OUTPUT_HANDLE),&cursor_info);
}


int startup()                   //数据初始化
{

    HideCursor();           //隐藏光标
    //屏幕尺寸

    int i,j;

    //以下设定边框数值
    for(i=0;i<High;i++)
    {
        canvas[i][0]=-1;
        canvas[i][Width-1]=-1;
    }
      for(j=0;j<Width;j++)
    {
        canvas[0][j]=-1;
        canvas[High-1][j]=-1;
    }
    //以下初始化蛇头蛇身
    canvas[High/2][Width/2]=1;

    for(i=0;i<=4;i++)
    {
        canvas[High/2][Width/2-i]=i+1;
    }

    //初始化小蛇移动方向向右
    moveDirection=4;

    //初始化食物的位置
    food_x=rand()%(High-5)+2;
    food_y=rand()%(Width-5)+2;
    canvas[food_x][food_y]=-2;


}

void moveSnakeByDirection()
{
    int i,j;
    int max=0;
    int oldTail_i,oldTail_j;    //记录旧蛇尾的位置
    int oldHead_i,oldHead_j;    //记录旧蛇头的位置
    for(i=1;i<High-1;i++)
    {
        for(j=1;j<Width;j++)
        {

            if(canvas[i][j]>0)
            {
                //对所有大于0的元素+1
                canvas[i][j]++;
                //求最大值
                if(max<canvas[i][j])
                {
                    max=canvas[i][j];
                    oldTail_i=i;
                    oldTail_j=j;
                }

                //记录旧蛇头位置
                if(canvas[i][j]==2)
                {
                    oldHead_i=i;
                    oldHead_j=j;
                }
            }

        }
    }

    int newHead_i,newHead_j;

    if(moveDirection==1)    //向上
    {
        newHead_i=oldHead_i-1;
        newHead_j=oldHead_j;
    }

    if(moveDirection==2)    //向下
    {
        newHead_i=oldHead_i+1;
        newHead_j=oldHead_j;
    }

    if(moveDirection==3)    //向左
    {
        newHead_i=oldHead_i;
        newHead_j=oldHead_j-1;
    }

    if(moveDirection==4)    //向上
    {
        newHead_i=oldHead_i;
        newHead_j=oldHead_j+1;
    }

    //判断小蛇蛇头是否碰到食物
    if(canvas[newHead_i][newHead_j]==-2)
    {
        //食物原始位置归0
        canvas[food_x][food_y]=0;

        //产生新的食物
        food_x=rand()%(High-5)+2;
        food_y=rand()%(Width-5)+2;
        canvas[food_x][food_y]=-2;

        //吃到食物不用把最大值设为0，长度+1

    }
    else
    {
        //没有吃到食物的时候，长度不变
        canvas[oldTail_i][oldTail_j]=0;     //最大值所在元素变为0
    }

    //判断小蛇蛇头撞到边框或自身游戏失败
    if(canvas[newHead_i][newHead_j]>0||canvas[newHead_i][newHead_j]==-1)
    {
        printf("游戏失败\n");
        exit(0);
    }
    else
    {
        canvas[newHead_i][newHead_j]=1;
    }

}

int show()                    //显示画面
{
    gotoxy(0,0);            //清屏
    int i,j;
    for(i=0;i<High;i++)
    {
        for(j=0;j<Width;j++)
        {
            if(canvas[i][j]==0)
                printf(" ");       //输出空格
            else if(canvas[i][j]==-1)
                printf("#");        //输出边框
            else if(canvas[i][j]==1)
                printf("@");        //输出蛇头
            else if(canvas[i][j]>1)
                printf("*");        //输出蛇身
            else if(canvas[i][j]==-2)
                printf("F");        //输出食物

        }
        printf("\n");
    }

    Sleep(100);

}


int updateWithoutput()      //与用户输入无关的更新
{
    moveSnakeByDirection();


}

int updateWithinput()     //与用户输入有关的更新
{
    char input;
    if(kbhit())     //当按键时执行
    {
			input = getch();  // 根据用户的不同输入来移动，不必输入回车

            if(input=='a')
                moveDirection=3;
            if(input=='d')
                moveDirection=4;
            if(input=='w')
                moveDirection=1;
            if(input=='s')
                moveDirection=2;
    }
}



int main()
{
	startup();          //数据初始化
	while(1)            //游戏循环执行
    {
        show();          //显示画面
        updateWithoutput();     //与用户输入无关的更新
        updateWithinput();     //与用户输入有关的更新
    }
    return 0;
}